#ifndef vector3f_H
#define vector3f_H
#include <iostream>
#include <math.h>
using namespace std;

/*
 * a 3D vector class, not dynamic array:)
 * */
class vector3f {
public:

	float x, y, z;

	void setValue(float x, float y, float z) {
		this->x = x;
		this->y = y;
		this->z = z;
	}

	vector3f(float x = 0, float y = 0, float z = 0) :
		x(x), y(y), z(z) {
	}

	bool operator ==(const vector3f p) {
		return x == p.x && y == p.y && z == p.z;
	}

	bool operator !=(const vector3f p) {
		return x != p.x || y != p.y || z != p.z;
	}

	vector3f operator +(vector3f p) {
		return vector3f(x + p.x, y + p.y, z + p.z);
	}

	vector3f operator -(vector3f p) {
		return vector3f(x - p.x, y - p.y, z - p.z);
	}

	float operator *(vector3f p) /* dot product */
	{
		return x * p.x + y * p.y + z * p.z;
	}

	vector3f operator ^(vector3f p) /* cross product */
	{
		return vector3f(y * p.z - p.y * z, -(x * p.z - p.x * z), x * p.y - p.x
				* y);
	}

	vector3f normalize() {
		float len;
		len = (float) (sqrt(x * x + y * y + z * z));
		return vector3f(x / len, y / len, z / len);
	}

	float length() {
		return (float) (sqrt(x * x + y * y + z * z));
	}

	float squaredLength() {
		return x * x + y * y + z * z;
	}

	vector3f perp1();
	vector3f perp2();
};

vector3f operator *(float k, vector3f const& p);

float distToEdge(vector3f point, vector3f head, vector3f tail);

ostream& operator <<(ostream& stream, vector3f const& p);
istream& operator >>(istream& stream, vector3f & p);

#endif
